/**
 * Code modified from Firefox add-on Ambient News by
 * Contributor(s):
 *  Atul Varma <avarma@mozilla.com>
 *  Ben Basson <ben@basson.at>
 */
 
function loadDoubanPage() {

	var jsm = {};
	Components.utils.import("resource://douban-modules/bridge.js", jsm);
	var subjects = jsm.DoubanBridge.getDoubanBuddy().hots;
	var lastUpdate = jsm.DoubanBridge.getDoubanBuddy().lastupdate;
	if (subjects && subjects.length > 0) {
		var text = getHtmlSource(subjects, lastUpdate);
		if (text) {
			$(text).appendTo("#content");
		}
	} else {
		var status = jsm.DoubanBridge.getDoubanBuddy().status;
		var text = '<h1>请阅读下面的提示信息</h1><div class="message">';
		if (status == "refresh") {
			text += '<p>正在读取您豆瓣上的友邻最近的广播内容<b>（大约需要5分钟）</b>，请稍后刷新本页面：</p>';
			text += '<p class="info">\u00b7 <a href="about:douban" target="_self">点击刷新</a></p>';
		} else {
			text += '<p>豆瓣好友是建立在Firefox基础上的附加组件，他利用豆瓣提供的API来访问您在豆瓣上的友邻广播内容。</p>';
			text += '<p>为了保护豆瓣用户的数据，作为第三方应用，豆瓣好友需要访问受保护的用户数据，因此，需要通过一套稍微复杂的流程来获取用户的授权<b>（放心，豆瓣好友会帮助您）</b>，从而实现豆瓣好友热点发现的功能：</p>';
			if (status == "request") {
				text += '<p class="info">\u00b7 正在请求授权口令</p>';
				text += '<p class="info">\u00b7 刷新页面进入下一步</p>';
				text += '<p class="info">\u00b7 <a href="about:douban" target="_self">点击刷新</a></p>';
			} else if (status.indexOf("auth@") == 0) {
				text += '<p>您需要对豆瓣好友的访问提供授权，点击下面的链接：</p>';
				text += '<p class="info">\u00b7 <a href="' + status.substring(5) + '">点击这里会打开豆瓣的授权页面，在那里点击<b>同意</b></a></p>';
				text += '<p>如果您已经点过同意，请点击下面的链接：</p>';
				text += '<p class="info">\u00b7 <a href="about:douban" onclick="auth();" target="_self">我已授权</a></p>';				
			} else if (status == "access") {
				text += '<p class="info">\u00b7 完成授权，正在请求访问口令</p>';
				text += '<p class="info">\u00b7 刷新页面进入下一步</p>';
				text += '<p class="info">\u00b7 <a href="about:douban" target="_self">点击刷新</a></p>';
			}
		}
		text += "</div>";
		text += '<p style="padding-left: 30px;"><a href="http://www.douban.com/tour"><img src="chrome://doubanbuddy/content/res/tour.jpg"/></a></p>';
		$(text).appendTo("#content");	
	}

	$("#searchBox").focus();
	
	loadDoubanItems();
	loadDoubanNews();
}

function auth() {
	var jsm = {};
	Components.utils.import("resource://douban-modules/bridge.js", jsm);
	jsm.DoubanBridge.getDoubanBuddy().completeAuth();
}

function loadDoubanItems() {
	var _feeds = new Array();
	$("div > .item").each(function() {
		var itemContent = $(".itemContent[id]", this);
		if (itemContent && $(itemContent).attr("id") && $(itemContent).attr("id") != "") {
			_feeds.push($(itemContent).attr("id"));
		}
	});
	
	var _feedIndex = 0;
	var _shownFeeds = {};
	
	function __getNextFeed() {
		if (_feedIndex == _feeds.length)
			return;
			
		var feedUri = unescape(_feeds[_feedIndex]);
		_feedIndex++;
		if (feedUri in _shownFeeds) {
			__getNextFeed();
		} else {
			_shownFeeds[feedUri] = true;
			DoubanNews.getFeed(feedUri, __displayFeed);
		}
	}
	
	function __displayFeed(feed) {
		if (feed && feed.title.text in _shownFeeds)
			// We've already shown this feed, skip to the next one.
			feed = null;
			
		if (feed) {
			_shownFeeds[feed.title.text] = true;
			var text = "";
			var entriesToShow = 5;
			var useAuthor = false;
			if (feed.entries.length < entriesToShow)
				entriesToShow = feed.entries.length;
			if (entriesToShow > 1 &&
						feed.entries[0].title.text == feed.entries[1].title.text)
				// The feed's entries all have the same title, so display
		        // author information instead.  This is used for Vanilla
				// thread feeds.
				useAuthor = true;
			var feedLink = feed.link ? feed.link.spec : "";
			text += ('<div class="feed"><ul><li class=\"feed-entry\">更多信息</li>');
			for (var i = 0; i < entriesToShow; i++) {
				var entryTitle = feed.entries[i].title.text;
				if (useAuthor) {
			    	entryTitle = feed.entries[i].authors.queryElementAt(
           								0,
							            Components.interfaces.nsIFeedPerson
         								).name;
				}
				if (entryTitle.length > 35) {
      				entryTitle = entryTitle.slice(0, 35) + '\u2026';
       			}
       			text += ('<li class="feed-entry ita"> \u00b7 <a href="' +
                			feed.entries[i].link.spec +
                			'"><span style="' + getRandomSpanStyle() + '">' +
                 			entryTitle + '</span></a></li>');
   			}
			text += '</ul></div>';
			var itemContent = $("div .item .itemContent[id=" + _feeds[_feedIndex - 1] + "]");
			$(text).hide().fadeIn("slow", __getNextFeed).appendTo($(itemContent));
		} else {
			// We're skipping this feed, so just process the next one.
			window.setTimeout(__getNextFeed, 10);
		}
	}
	
	__getNextFeed();
}

function loadDoubanNews() {
	var Cc = Components.classes;
	var Ci = Components.interfaces;
	var historyService = Cc["@mozilla.org/browser/nav-history-service;1"]
                       .getService(Ci.nsINavHistoryService);
	// No query parameters will get all history.
	var options = historyService.getNewQueryOptions();
	options.resultType = options.RESULTS_AS_URI;
	options.sortingMode = options.SORT_BY_VISITCOUNT_DESCENDING;

	// No query parameters will return everything.
	var query = historyService.getNewQuery();
	query.annotation = "douban/feed";

	var result = historyService.executeQuery(query, options);
	var root = result.root;
  	root.containerOpen = true;

	// Index of the feed number that we're looking at.
	var childNum = 0;

	// Number of feeds we've shown so far.
	var childrenShown = 0;

	// Maximum numer of feeds we'll show.
	var maxChildrenToShow = 15;

	// Hashtable that keeps track of what feeds we've shown so far,
	// holding both URLs and feed titles. The keys for the values are
	// irrelevant; we're just using a hashtable for quick lookup.
	var shownFeeds = {};

	// This function fetches the next feed and then displays it.
	function getNextFeed() {
		if (childrenShown == maxChildrenToShow ||
				childNum == root.childCount) {
			// We're done!  Close our query result container.
			root.containerOpen = false;
		} else {
			var annSvc = DoubanNews.__getAnnSvc();
			var child = root.getChild(childNum);
			var feedUri = null;
			try {
				feedUri = annSvc.getPageAnnotation(DoubanNews.url(child.uri), "douban/feed");
			} catch (e) {
			}
			childNum++;
			if (feedUri in shownFeeds) {
				// We've already shown this feed, skip to the next one.
				getNextFeed();
			} else {
				shownFeeds[feedUri] = true;
				childrenShown++;
				DoubanNews.getFeed(feedUri, displayFeed);
			}
		}
	}

	// This function displays the given feed.
	function displayFeed(feed) {
		if (feed && feed.title.text in shownFeeds)
			// We've already shown this feed, skip to the next one.
			feed = null;
			
		if (feed) {
			shownFeeds[feed.title.text] = true;
			var text = "";
			var entriesToShow = 5;
			var useAuthor = false;
			if (feed.entries.length < entriesToShow)
				entriesToShow = feed.entries.length;
			if (entriesToShow > 1 &&
						feed.entries[0].title.text == feed.entries[1].title.text)
				// The feed's entries all have the same title, so display
		        // author information instead.  This is used for Vanilla
				// thread feeds.
				useAuthor = true;
			var feedLink = feed.link ? feed.link.spec : "";
			text += ('<div class="feed"><div class="feed-title"><a ' +
						'href="' + feedLink + '">' +
						feed.title.text + '</a></div><ul>');
			for (var i = 0; i < entriesToShow; i++) {
				var entryTitle = feed.entries[i].title.text;
				if (useAuthor) {
			    	entryTitle = feed.entries[i].authors.queryElementAt(
           								0,
							            Components.interfaces.nsIFeedPerson
         								).name;
				}
				if (entryTitle.length > 35) {
      				entryTitle = entryTitle.slice(0, 35) + '\u2026';
       			}
       			text += ('<li class="feed-entry"> \u00b7 <a href="' +
                			feed.entries[i].link.spec +
                			'">' +
                 			entryTitle + '</a></li>');
   			}
			text += '</ul></div>';
			$(text).hide().fadeIn("slow", getNextFeed).appendTo("#sidebar");
		} else {
			// We're skipping this feed, so just process the next one.
			window.setTimeout(getNextFeed, 10);
		}
	}

	getNextFeed();

}

function getHtmlSource(subjects, lastUpdate) {
	var pageSource = "";
	pageSource += "<h1>豆瓣好友讨论的热点</h1>\n";
	pageSource += "<div id=\"hotHeader\"><small>最后更新：" + lastUpdate.toLocaleString() + "</small></div>\n";
	if (new Date().getTime() - lastUpdate.getTime() > 45 * 60 * 1000) {
		pageSource += '<div class="message"><p>豆瓣好友每一个小时自动抓取友邻广播内容进行分析，时间还没到，稍后再刷新～～</p></div>';
	}
	for (var i = 0; i < subjects.length; ++i) {
		pageSource += "<div class=\"item\" id=\"subject-" + i + "\">\n";
		pageSource += "		<div class=\"itemIcon\">\n";
		if (subjects[i].image != "") {
			pageSource += "			<a href=\"" + subjects[i].link + "\"><img src=\"" + subjects[i].image + "\" class=\"person\"/></a>\n";
		} else {
			pageSource += "			<a href=\"" + subjects[i].link + "\"><img src=\"res/user.jpg\" class=\"person\"/></a>\n";
		}
		pageSource += "		</div>\n";
   		var rssLink = getRssLink(subjects[i]);
   		if (rssLink && rssLink != "") 
			pageSource += "		<div class=\"itemContent\" id=\"" + escape(rssLink) + "\">\n";
		else 
			pageSource += "		<div class=\"itemContent\">\n";
   		pageSource += "			<div class=\"itemSummary\">\n";
   		pageSource += "				<a href=\"" + subjects[i].link + "\">" + subjects[i].title + "</a><br />" ;
   		pageSource += "				<small>" + getKindClass(subjects[i].kind) + " +" + subjects[i].hot + "°C</small>\n";
   		pageSource += "			</div>\n";
		pageSource += "         <div class=\"itemOther\">\n";
		if (subjects[i].description != "") {
    		pageSource += "			<p class=\"description\">\n";
    		pageSource += "         	" + subjects[i].description + "\n";
    		pageSource += "			</p>";				
		}
		if (subjects[i].comments.length > 0) {
			pageSource += '			<div class="feed"><ul><li class="feed-entry">评论</li>';
			for (var j = 0; j < subjects[i].comments.length; ++j) {
		   		pageSource += '			<li class="feed-entry ita">&nbsp;\u00b7&nbsp;';
	   			pageSource += "         	“" + subjects[i].comments[j] + "”\n";
	   			pageSource += "			</li>";
			}	
			pageSource += "</div>";
		}
		if (subjects[i].related.length > 0) {
			pageSource += '			<div class="feed"><ul><li class="feed-entry">类似热点</li>';
			for (var j = 0; j < subjects[i].related.length && j < 10; ++j) {
		   		pageSource += '			<li class="feed-entry ita">&nbsp;\u00b7&nbsp;';
	   			pageSource += "         	" + subjects[i].related[j] + "\n";
	   			pageSource += "			</li>";
			}	
			pageSource += "</div>";
		}
		
  		pageSource += "			</div>\n";
   		pageSource += "		</div>\n";
 		pageSource += "</div>\n";
	}
	return pageSource;
}
	
function getRssLink(subject) {
	var kind = subject.kind;
	var rssLink = "";
	if (kind == "movie" || kind == "book" || kind == "music" || kind == "tv" || kind == "magazine") {
		rssLink = "http://www.douban.com/feed/subject/" + subject.id + "/reviews";
	} else if (kind == "friend" || kind == "contact") {
		rssLink = "http://www.douban.com/feed/people/" + subject.id + "/interests";
	} else if (kind == "group") {
		rssLink = "http://www.douban.com/feed/group/" + subject.id + "/discussion";
	}
	return rssLink;
}

function getRandomSpanStyle() {
	var colors = ["rgb(102, 102, 102)", "rgb(153, 153, 153)", "rgb(170, 170, 170)", "rgb(153, 51, 102)",
				  "rgb(102, 0, 0)", "rgb(153, 0, 153)", "rgb(102, 153, 0)", "rgb(153, 102, 51)", "rgb(153, 0, 102)",
				  "rgb(0, 51, 0)", "rgb(0, 153, 51)", "rgb(51, 153, 51)", "rgb(51, 51, 51)", "rgb(102, 102, 51)"];
	var style = "color: " + colors[Math.floor(Math.random() * colors.length)] + ";";
	return style;
}
	

function getKindClass(kind) {
	var kindMap = {
		"book" : "书籍",
		"movie" : "电影",
		"music" : "音乐",
		"tv" : "电视",
		"magazine" : "杂志",
		"group" : "小组",
		"place" : "地点",
		"photo" : "照片",
		"url" : "分享网页地址",
		"friend" : "好友",
		"contact" : "好友",
		"entry" : "博客文章",
		"event" : "同城活动",
		"online" : "线上活动",
		"blog" : "博客文章",
		"photo_album" : "相册",
		"recommendation" : "推荐",
		"topic" : "小组话题",
		"note" : "日记",
		"review" : "评论",
		"video" : "视频",
		"doulist" : "豆列",
		"site" : "博客",
		"artist_video" : "音乐人视频",
		"discussion" : "讨论"
	};
		
	if (kindMap[kind])
		return kindMap[kind];
		
	return kind;
}

$(window).ready(loadDoubanPage);